//==========================================================================
// Copyright (c) 2000-2008,  Elastos, Inc.  All Rights Reserved.
//==========================================================================

#include <ddk.h>

EXTERN void DzYield();

EXTERN void SubThreadAbortMainThread();
EXTERN void AbortFinishedThread();
EXTERN void GetStateRunningOnlyByMyself();
EXTERN void CreateThreadMax();
EXTERN void SuspendResumeThread0();
EXTERN void SuspendResumeThread1();
EXTERN void GetThreadFinishCode();
EXTERN void GetThreadAllFinishCode();
EXTERN void GetThreadStartTime();
EXTERN void AbortThreadGetFinishCode();
EXTERN void JoinThreadReturn();
EXTERN void JoinThreadParameter();
EXTERN void ThreadGetId();
EXTERN void ThreadPrioritytst();
EXTERN void ThreadGetProcTime();
EXTERN void SubAbortMainThread();

class ThreadServer001 : public CDeviceDriver
{
public:
    CARAPI Read(
        /* [in] */ UInt64 u64Offset,
        /* [in] */ UInt32 bytesToRead,
        /* [out] */ EzByteBuf buffer,
        /* [out] */ IEvent * * ppCompletionEvent);

    CARAPI Write(
        /* [in] */ UInt64 u64Offset,
        /* [in] */ EzByteBuf buffer,
        /* [out] */ UInt32 * puNumberOfBytesWritten,
        /* [out] */ IEvent * * ppCompletionEvent);

    CARAPI Control(
        /* [in] */ Handle32 nControlCode,
        /* [in] */ EzByteBuf inBuffer,
        /* [out] */ EzByteBuf * pOutBuffer,
        /* [out] */ IEvent * * ppCompletionEvent);

    virtual void Dispose() {}
};

EXTERN IDeviceDriver * CDECL CreateThreadServer000(uint_t uDeviceNo,
    void *pvParameter)
{
    ThreadServer001 *pDriver = new ThreadServer001;
    if (NULL == pDriver) {
        kprintf("ERROR:There have no enough memory, %s, %d\n",
                        __FILE__, __LINE__);
        return NULL;
    }

    pDriver->AddRef();

    return pDriver;
}

ECode ThreadServer001::Read(
    /* [in] */ UInt64 u64Offset,
    /* [in] */ UInt32 bytesToRead,
    /* [out] */ EzByteBuf buffer,
    /* [out] */ IEvent * * ppCompletionEvent)
{
    return E_NOT_IMPLEMENTED;
}

ECode ThreadServer001::Write(
    /* [in] */ UInt64 u64Offset,
    /* [in] */ EzByteBuf buffer,
    /* [out] */ UInt32 * puNumberOfBytesWritten,
    /* [out] */ IEvent * * ppCompletionEvent)
{
    return E_NOT_IMPLEMENTED;
}

ECode ThreadServer001::Control(
    /* [in] */ Handle32 nControlCode,
    /* [in] */ EzByteBuf inBuffer,
    /* [out] */ EzByteBuf * pOutBuffer,
    /* [out] */ IEvent * * ppCompletionEvent)
{
    if (NULL != ppCompletionEvent || !pOutBuffer->IsNull()) {
        return E_INVALID_ARGUMENT;
    }

    ECode ec = NOERROR;

    switch (nControlCode) {
        case 0:{
            if (!inBuffer.IsNull()) {
                return E_INVALID_ARGUMENT;
            }

            SubThreadAbortMainThread();

            break;
        }

        case 1:{
            if (!inBuffer.IsNull()) {
                return E_INVALID_ARGUMENT;
            }

            AbortFinishedThread();

            break;
        }

        case 2:{
            if (!inBuffer.IsNull()) {
                return E_INVALID_ARGUMENT;
            }

            GetStateRunningOnlyByMyself();

            break;
        }

        case 3:{
            if (!inBuffer.IsNull()) {
                return E_INVALID_ARGUMENT;
            }

            SubAbortMainThread();

            break;
        }

        case 4:{
            if (!inBuffer.IsNull()) {
                return E_INVALID_ARGUMENT;
            }

            SuspendResumeThread0();

            break;
        }

        case 5:{
            if (!inBuffer.IsNull()) {
                return E_INVALID_ARGUMENT;
            }

            SuspendResumeThread1();

            break;
        }

        case 6:{
            if (!inBuffer.IsNull()) {
                return E_INVALID_ARGUMENT;
            }

            GetThreadFinishCode();

            break;
        }

        case 7:{
            if (!inBuffer.IsNull()) {
                return E_INVALID_ARGUMENT;
            }

            GetThreadAllFinishCode();

            break;
        }

        case 8:{
            if (!inBuffer.IsNull()) {
                return E_INVALID_ARGUMENT;
            }

            GetThreadStartTime();

            break;
        }

        case 9:{
            if (!inBuffer.IsNull()) {
                return E_INVALID_ARGUMENT;
            }

            AbortThreadGetFinishCode();

            break;
        }

        case 10:{
            if (!inBuffer.IsNull()) {
                return E_INVALID_ARGUMENT;
            }

            JoinThreadReturn();

            break;
        }

        case 11:{
            if (!inBuffer.IsNull()) {
                return E_INVALID_ARGUMENT;
            }

            JoinThreadParameter();

            break;
        }

        case 12:{
            if (!inBuffer.IsNull()) {
                return E_INVALID_ARGUMENT;
            }

            ThreadGetId();

            break;
        }

        case 13:{
            if (!inBuffer.IsNull()) {
                return E_INVALID_ARGUMENT;
            }

            ThreadPrioritytst();

            break;
        }

        case 14:{
            if (!inBuffer.IsNull()) {
                return E_INVALID_ARGUMENT;
            }

            ThreadGetProcTime();

            break;
        }

        default:{
            return E_NOT_IMPLEMENTED;
        }
    }

    return ec;
}
